package com.go.where.family.api.servlet;

import java.io.IOException;
import java.util.UUID;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.apache.log4j.Logger;

import com.go.where.family.api.constants.Constant;
import com.go.where.family.api.scoket.Head;
import com.go.where.family.api.scoket.SocketDTO;
import com.go.where.family.api.scoket.TransmissionCode;
import com.go.where.family.api.server.HttpServerStartMain;
import com.go.where.family.api.utils.CommonUtil;
import com.go.where.family.api.utils.IpUtil;
import com.go.where.family.api.utils.MD5Util;
import com.go.where.family.api.utils.ServletUtil;
import com.go.where.family.api.vo.UserResultVo;
import com.go.where.family.api.vo.UserVo;
import com.google.gson.Gson;

/**
 * 绑定第三方账号接口
 * 
 * @description
 * @author
 * @date
 */
public class BindAccountServlet extends SuperServlet {

	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;

	private static Logger log = Logger.getLogger(BindAccountServlet.class);
	private static Gson gson = CommonUtil.gson();

	@Override
	protected void doGet(HttpServletRequest req, HttpServletResponse resp)
			throws ServletException, IOException {
		doPost(req, resp);
	}

	@Override
	protected void doPost(HttpServletRequest req, HttpServletResponse resp)
			throws ServletException, IOException {
		req.setAttribute("org.eclipse.jetty.server.Request.queryEncoding",
				"UTF-8");
		resp.setContentType("text/html;charset=UTF-8");
		resp.setStatus(HttpServletResponse.SC_OK);

		// 手机号码
		String phoneNumber = req.getParameter("phoneNumber");
		String customerId = req.getParameter("customerId");
		String account = req.getParameter("account");
		String accountType = req.getParameter("accountType");
		String bindOrNot = req.getParameter("bindOrNot");
		// 校验密文
		String sign = req.getParameter("sign");
		String deviceId = req.getParameter("deviceId");

		log.info("绑定账号：phoneNumber：" + phoneNumber + ",customerId："
				+ customerId + ",account：" + account + ",accountType："
				+ accountType + ",bindOrNot：" + bindOrNot + ",deviceId："
				+ deviceId + ",sign：" + sign);
		boolean flag = this.validateData(phoneNumber, customerId, account,
				accountType, bindOrNot, sign, resp, req);
		UserResultVo ri = new UserResultVo();
		if (flag) {// 数据校验成功
			try {
				boolean check = super.checkUser(req, resp);
				if (!check) {
					return;
				}
				UserVo user = new UserVo();
				user.setMobile(phoneNumber);
				user.setAccount(account);
				user.setAccountType(accountType);
				user.setBindOrNot(bindOrNot);
				user.setCustomerId(customerId);
				SocketDTO dto = sendMessage(user, req);
				Head head = dto.getHead();
				String resCode = head.getResponseCode();
				// String resMsg = head.getResponseMessage();
				String body = dto.getBody();
				if (TransmissionCode.SUCCESS.getCode().equals(resCode)) {
					// 把service中返回的信息转成对应的json格式字符串，返回给接口调用者
					if (StringUtils.isNotBlank(body)) {
						boolean result = gson.fromJson(body, Boolean.class);
						if (result) {
							ri.setCode(Constant.SUCCESS);
							ri.setStatus(Constant.TRUE);
							ServletUtil.writeResJsonStr(resp, CommonUtil.gson()
									.toJson(ri));
						} else {
							ServletUtil.writeErrorStr(resp);
						}
					} else {
						ServletUtil.writeErrorStr(resp);
					}
				} else if (TransmissionCode.ACCOUNT_BINDED.getCode().equals(
						resCode)) {
					log.error("内部通信，" + head.getResponseMessage());
					ri.setCode(Constant.ACCOUNT_BINDED);
					ri.setStatus(Constant.FALSE);
					ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
				} else if (TransmissionCode.ACCOUNT_BIND_MUST_ONE.getCode().equals(
						resCode)) {
					log.error("内部通信，" + head.getResponseMessage());
					ri.setCode(Constant.ACCOUNT_BIND_MUST_ONE);
					ri.setStatus(Constant.FALSE);
					ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
				} else {
					log.error("内部通信异常，" + head.getResponseMessage());
					ServletUtil.writeErrorStr(resp);
				}
			} catch (Exception e) {
				log.error("异常信息", e);
				// 异常情况，也把对应异常信息的json格式字符串返回给接口调用者
				ServletUtil.writeErrorStr(resp);
			}
		}
	}

	/**
	 * 向service服务发送请求
	 * 
	 * @param t
	 * @param req
	 * @return
	 */
	private SocketDTO sendMessage(UserVo user, HttpServletRequest req) {
		Head head = new Head();
		head.setRequestId(UUID.randomUUID().toString());
		head.setServiceCode(Constant.BIND_3PART_ACCOUNT);
		head.setIp(IpUtil.getIpAddr(req));
		head.setUserId("api");
		return super.send(head, user);
	}

	/**
	 * 数据校验合法性
	 * 
	 * @param id
	 * @param name
	 * @param sign
	 * @param resp
	 * @param req
	 * @return
	 * @throws IOException
	 */
	private boolean validateData(String phoneNumber, String customerId,
			String account, String accountType, String bindOrNot, String sign,
			HttpServletResponse resp, HttpServletRequest req)
			throws IOException {
		boolean result = false;
		UserResultVo ri = new UserResultVo();
		if (StringUtils.isEmpty(customerId)) {
			log.info("用户账号为空!!!");
			ri.setCode(Constant.USER_IS_NULL);
			ri.setStatus(Constant.FALSE);
			ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
			return false;
		} else if (StringUtils.isEmpty(bindOrNot)) {
			log.info("绑定标识为空!!!");
			ri.setCode(Constant.BIND_MARK_IS_NULL);
			ri.setStatus(Constant.FALSE);
			ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
			return false;
		} else if (StringUtils.isEmpty(sign)) {
			log.info("签名字符串为空!!!");
			ri.setCode(Constant.SIGN_IS_NULL);
			ri.setStatus(Constant.FALSE);
			ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
			return false;
		} else {
			String key = HttpServerStartMain.getValue("go.where.family.key");
			StringBuilder builder = new StringBuilder();
			if (StringUtils.isNotBlank(account)) {
				builder.append("account");
				builder.append(account);
			}
			if (StringUtils.isNotBlank(accountType)) {
				builder.append("accountType");
				builder.append(accountType);
			}
			if (StringUtils.isNotBlank(bindOrNot)) {
				builder.append("bindOrNot");
				builder.append(bindOrNot);
			}
			if (StringUtils.isNotBlank(customerId)) {
				builder.append("customerId");
				builder.append(customerId);
			}
			if (StringUtils.isNotBlank(phoneNumber)) {
				builder.append("phoneNumber");
				builder.append(phoneNumber);
			}
			builder.append("key");
			builder.append(key);

			String data = builder.toString();

			boolean checked = MD5Util.checkMD5Signature(data, sign);
			if (checked) {
				result = true;
			} else {
				log.info("数字签名失败！！！");
				ri.setCode(Constant.CHECK_SIGN_FAIL);
				ri.setStatus(Constant.FALSE);
				ServletUtil.writeResJsonStr(resp, gson.toJson(ri));
				return false;
			}
		}

		return result;
	}
}
